home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Atari Mega Archive 2
/
Atari Mega Archive CD - Volume 2.iso
/
linux
/
tools
/
gtar10.lha
/
port.c
< prev
next >
Wrap
C/C++ Source or Header
|
1992-09-09
|
28KB
|
1,329 lines
/* Supporting routines which may sometimes be missing.
Copyright (C) 1988 Free Software Foundation
This file is part of GNU Tar.
GNU Tar is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 1, or (at your option)
any later version.
GNU Tar is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GNU Tar; see the file COPYING. If not, write to
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
/*
* @(#)port.c 1.15 87/11/05 by John Gilmore, 1986
*
* These are routines not available in all environments.
*
* I know this introduces an extra level of subroutine calls and is
* slightly slower. Frankly, my dear, I don't give a damn. Let the
* Missed-Em Vee losers suffer a little. This software is proud to
* have been written on a BSD system.
*/
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <signal.h>
#include <errno.h>
#if defined(__MSDOS__) || defined(USG)
#include <fcntl.h>
#else
#include <sys/file.h>
#endif
#include "tar.h"
#include "port.h"
#ifdef USG
#include <string.h>
#else
extern size_t strlen();
#endif
extern long baserec;
/*
* Some people (e.g. V7) don't have a #define for these.
*/
#ifndef O_BINARY
#define O_BINARY 0
#endif
#ifndef O_RDONLY
#define O_RDONLY 0
#endif
#ifndef NULL
#define NULL 0
#endif
/* JF: modified so all configuration information can appear here, instead of
being scattered through the file. Add all the machine-dependent #ifdefs
here */
#undef WANT_DUMB_GET_DATE/* WANT_DUMB_GET_DATE --> get_date() */
#undef WANT_VALLOC /* WANT_VALLOC --> valloc() */
#undef WANT_MKDIR /* WANT_MKDIR --> mkdir() rmdir() */
#undef WANT_STRING /* WANT_STRING --> index() bcopy() bzero() bcmp() */
#undef WANT_BZERO /* WANT_BZERO --> bzero() bcmp() execlp() */
/* EMUL_OPEN3 --> open3() */
#undef WANT_MKNOD /* WANT_MKNOD --> mknod() link() chown() geteuid() */
#undef WANT_UTILS /* WANT_UTILS --> panic() ck_*() *_buffer()
merge_sort() quote_copy_string() un_quote_string() */
#undef WANT_CK_PIPE /* WANT_CK_PIPE --> ck_pipe() */
#undef WANT_GETWD /* WANT_GETWD --> getwd() */
#undef WANT_STRSTR /* WANT_STRSTR --> strstr() */
#undef WANT_FTRUNCATE /* WANT_FTRUNCATE --> frtruncate() */
/* Define only ONE of these four . . . */
/* #undef DOPRNT_MSG /* Define this one if you have _doprnt() and
no varargs support */
/* #undef VARARGS_MSG /* Define this one if you have varargs.h and
vfprintf() */
/* #undef STDC_MSG /* Define this one if you are using ANSI C and
and have vfprintf() */
/* #undef LOSING_MSG /* Define this one if you don't have any of the
above */
#ifdef USG
#define WANT_STRING
#define WANT_VALLOC
#if defined(sgi) && defined(mips)
#define WANT_GETWD
#endif
#if defined(i386)
#define WANT_FTRUNCATE
#endif
#endif
#ifdef hpux
#define WANT_VALLOC
#endif
#ifdef MINIX
#define WANT_BZERO
#endif
#ifdef __MSDOS__
char TTY_NAME[] = "con";
#define WANT_STRING
#define WANT_MKNOD
#define WANT_UTILS
#define WANT_VALLOC
#if (!defined(STDC_MSG) && !defined(DOPRNT_MSG) && !defined(VARARGS_MSG) && !defined(LOSING_MSG))
#ifdef __STDC__
#define STDC_MSG
#else
#define LOSING_MSG
#endif
#endif
#else /* not MSDOS */
#ifdef amigados
char TTY_NAME[] = "*";
#else
char TTY_NAME[] ="/dev/tty";
#endif
#define WANT_UTILS
#define WANT_CK_PIPE
#ifndef HAVE_STRSTR
#define WANT_STRSTR
#endif
#if (!defined(STDC_MSG) && !defined(DOPRNT_MSG) && !defined(VARARGS_MSG) && !defined(LOSING_MSG))
#ifdef BSD42
/* BSD systems should do this even if __STDC__, because
we might be using an ANSI compiler without an ANSI library. (sigh) */
#ifdef sparc
#define LOSING_MSG
#else
#define DOPRNT_MSG
#endif
#else /* not BSD */
#ifdef __STDC__
#define STDC_MSG
#else /* not ANSI C */
#define LOSING_MSG
#endif /* not ANSI C */
#endif /* not BSD */
#endif /* Need to define some form of _MSG */
#endif /* not MSDOS */
/* End of system-dependent #ifdefs */
#ifdef WANT_DUMB_GET_DATE
/* JF a get_date() routine takes a date/time/etc and turns it into a time_t */
/* This one is a quick hack I wrote in about five minutes to see if the N
option works. Someone should replace it with one that works */
/* This get_date takes an arg of the form mm/dd/yyyy hh:mm:ss and turns it
into a time_t . Its not well tested or anything. . . */
/* In general, you should use the get_date() supplied in getdate.y */
#define OFF_FROM GMT 18000 /* Change for your time zone! */
time_t
get_date(str)
char *str;
{
int month,day,year,hour,minute,second;
time_t ret;
int n;
#define SECS_PER_YEAR (365L*SECS_PER_DAY)
#define SECS_PER_LEAP_YEAR (366L*SECS_PER_DAY)
#define SECS_PER_DAY (24L*60*60)
static int days_per_month[2][12] = {
31,28,31,30,31,30,31,31,30,31,30,31,
31,29,31,30,31,30,31,31,30,31,30,31
};
static int days_per_year[2]={365,366};
month=day=year=hour=minute=second=0;
n=sscanf(str,"%d/%d/%d %d:%d:%d",&month,&day,&year,&hour,&minute,&second);
if(n<3)
return 0;
if(year<100)
year+=1900;
if(year<1970)
return 0;
ret=0;
ret+=OFF_FROM_GMT;
for(n=1970;n<year;n++)
if(n%4==0 && n%400!=0)
ret+=SECS_PER_LEAP_YEAR;
else
ret+=SECS_PER_YEAR;
month--;
for(n=0;n<month;n++) {
if(year%4==0 && year%400!=0)
ret+=SECS_PER_DAY*days_per_month[1][n];
else
ret+=SECS_PER_DAY*days_per_month[0][n];
}
ret+=SECS_PER_DAY*(day-1);
ret+=second+minute*60+hour*60*60;
return ret;
}
#endif
#ifdef WANT_VALLOC
/*
* valloc() does a malloc() on a page boundary. On some systems,
* this can make large block I/O more efficient.
*/
char *
valloc (size)
unsigned size;
{
extern char *malloc ();
return (malloc (size));
}
#endif
/*
* NMKDIR.C
*
* Written by Robert Rother, Mariah Corporation, August 1985.
*
* I wrote this out of shear disgust with myself because I couldn't
* figure out how to do this in /bin/sh.
*
* If you want it, it's yours. All I ask in return is that if you
* figure out how to do this in a Bourne Shell script you send me
* a copy.
* sdcsvax!rmr or rmr@uscd
*
* Severely hacked over by John Gilmore to make a 4.2BSD compatible
* subroutine. 11Mar86; hoptoad!gnu
*
* Modified by rmtodd@uokmax 6-28-87 -- when making an already existing dir,
* subroutine didn't return EEXIST. It does now.
*/
/*
* Make a directory. Compatible with the mkdir() system call on 4.2BSD.
*/
#ifdef WANT_MKDIR
int
mkdir(dpath, dmode)
char *dpath;
int dmode;
{
int cpid, status;
struct stat statbuf;
extern int errno;
if (stat(dpath,&statbuf) == 0) {
errno = EEXIST; /* Stat worked, so it already exists */
return -1;
}
/* If stat fails for a reason other than non-existence, return error */
if (errno != ENOENT) return -1;
switch (cpid = fork()) {
case -1: /* Error in fork() */
return(-1); /* Errno is set already */
case 0: /* Child process */
/*
* Cheap hack to set mode of new directory. Since this
* child process is going away anyway, we zap its umask.
* FIXME, this won't suffice to set SUID, SGID, etc. on this
* directory. Does anybody care?
*/
status = umask(0); /* Get current umask */
status = umask(status | (0777 & ~dmode)); /* Set for mkdir */
execl("/bin/mkdir", "mkdir", dpath, (char *)0);
_exit(-1); /* Can't exec /bin/mkdir */
default: /* Parent process */
while (cpid != wait(&status)) ; /* Wait for kid to finish */
}
if (TERM_SIGNAL(status) != 0 || TERM_VALUE(status) != 0) {
errno = EIO; /* We don't know why, but */
return -1; /* /bin/mkdir failed */
}
return 0;
}
int
rmdir(dpath)
char *dpath;
{
int cpid, status;
struct stat statbuf;
extern int errno;
if (stat(dpath,&statbuf) != 0) {
/* Stat just set errno. We don't have to */
return -1;
}
switch (cpid = fork()) {
case -1: /* Error in fork() */
return(-1); /* Errno is set already */
case 0: /* Child process */
execl("/bin/rmdir", "rmdir", dpa